﻿using BabyPoetryConference.Base;
using BabyPoetryConference.Extensions;
using Microsoft.Extensions.Configuration;
using NLog;
using NPOI.HSSF.Util;
using NPOI.SS.UserModel;
using NPOI.SS.Util;
using NPOI.XSSF.UserModel;
using NPOI.XWPF.UserModel;
using System;
using System.Collections.Generic;
using System.IO;
using System.Text;
using BabyPoetryConference.Entities;

namespace BabyPoetryConference.Services
{
    public class ToFileService
    {
        private static readonly Logger _Logger = LogManager.GetCurrentClassLogger();
        private IConfiguration _Config;
        private IQuestionService _QuestionService;
        private ICellStyle HeadStyle = null;
        private ICellStyle ContentStyle = null;
        public ToFileService(IConfiguration config, IQuestionService questionService)
        {
            _Config = config;
            _QuestionService = questionService;
        }

        #region 生成诗词问卷
        /// <summary>
        /// 生成诗词问卷
        /// </summary>
        /// <returns></returns>
        public string QuestionToWord(string postfix)
        {
            List<Question> qs = new List<Question>();
            var questionsCount = _Config.GetSection("to_word").GetInt("questions_count");
            for(var i = 0; i < questionsCount; i++)
            {
                qs.Add(_QuestionService.GetQuestion());
            }
            var now = DateTime.Now.ToString("yyyyMMddHHmmss");
            var wordPath = _Config.GetSection("path").GetString("word_path");
            var fileName = string.IsNullOrEmpty(postfix)? $"来自诗词大会的挑战_{ now}.docx" : $"来自诗词大会的挑战_{ now}_{postfix}.docx";
            var filePath = Path.Combine(wordPath, fileName);
            using (var fs = new FileStream(filePath, FileMode.Create, FileAccess.Write))
            {
                XWPFDocument doc = new XWPFDocument();
                var j = 1;
                foreach (var question in qs)
                {
                    AddHead(doc, $"问题 {j}");
                    AddContent(doc, question.Content.Replace("□", " __ "));
                    j++;
                }
                AddPageBreak(doc);

                doc.Write(fs);
            }
            return fileName;
        }

        public string AnswerToWord(string postfix)
        {
            List<Question> qs = new List<Question>();
            var questionsCount = _Config.GetSection("to_word").GetInt("questions_count");
            for (var i = 0; i < questionsCount; i++)
            {
                qs.Add(_QuestionService.GetQuestion());
            }
            var now = DateTime.Now.ToString("yyyyMMddHHmmss");
            var wordPath = _Config.GetSection("path").GetString("word_path");
            var fileName = string.IsNullOrEmpty(postfix) ? $"来自诗词大会的答案_{ now}.docx" : $"来自诗词大会的答案_{ now}_{postfix}.docx";
            var filePath = Path.Combine(wordPath, fileName);
            using (var fs = new FileStream(filePath, FileMode.Create, FileAccess.Write))
            {
                XWPFDocument doc = new XWPFDocument();
                var j = 1;
                foreach (var question in qs)
                {
                    AddHead(doc, $"答案 {j}");
                    AddContent(doc, question.Answer);
                    if(question.Subject.Equals("question", StringComparison.OrdinalIgnoreCase))
                    {
                        AddContent(doc, question.Explain);
                    }
                    j++;
                }
                AddPageBreak(doc);

                doc.Write(fs);
            }
            return fileName;
        }
        #endregion

        #region 打印诗词列表
        public string PoemsToWord()
        {
            List<Poem> qs = new List<Poem>();
            var poemKeys = _QuestionService.PoetryDict.Keys;
            var poemsAll = _Config.GetSection("to_word").GetBoolean("poetrys_all");

            var now = DateTime.Now.ToString("yyyyMMddHHmmss");
            var wordPath = _Config.GetSection("path").GetString("word_path");
            var fileName = $"诗词列表_{ now}.docx";
            var filePath = Path.Combine(wordPath, fileName);
            using (var fs = new FileStream(filePath, FileMode.Create, FileAccess.Write))
            {
                XWPFDocument doc = new XWPFDocument();
                var i = 1;
                foreach (var key in poemKeys)
                {
                    var poetry_content = "";
                    if (poemsAll)
                    {
                        poetry_content = _QuestionService.PoetryDict[key].GetContent();
                    }
                    else
                    {
                        var sentence = _QuestionService.PoetryDict[key].Sentences[0];
                        poetry_content = $"{key}  （{sentence.Substring(0, sentence.Length - 1)}）";
                    }
                    AddContent(doc, $"{i}. {poetry_content}");
                    i++;
                }

                doc.Write(fs);
                _Logger.Info($"生成诗词汇总到{filePath}");
            }
            return fileName;
        }
        #endregion

        #region 生成题库
        /// <summary>
        /// 把所有问题输出到Excel表格中
        /// </summary>
        public string AllQuestionsOfAllPoemsToExcel(out int count)
        {
            var all = _QuestionService.GetAllQuestionsOfAllPoems();
            count = all.Count;
            var now = DateTime.Now.ToString("yyyyMMddHHmmss");
            var wordPath = _Config.GetSection("path").GetString("word_path");
            var fileName = $"诗词题目_{ now}.xlsx";
            var filePath = Path.Combine(wordPath, fileName);

            using (var fs = new FileStream(filePath, FileMode.Create, FileAccess.Write))
            {

                IWorkbook workbook = new XSSFWorkbook();
                ISheet sheet = workbook.CreateSheet("诗词题目");
                // 标题
                var row = sheet.CreateRow(0);
                AddExcelHead(workbook, row, 0, "名称");
                AddExcelHead(workbook, row, 1, "类型");
                AddExcelHead(workbook, row, 2, "问题");
                AddExcelHead(workbook, row, 3, "答案");
                AddExcelHead(workbook, row, 4, "解释");

                //内容
                var i = 1;
                foreach (var question in all)
                {
                    var rowContent = sheet.CreateRow(i);
                    AddExcelCell(rowContent, 0, question.No);
                    AddExcelCell(rowContent, 1, question.BuildType);
                    AddExcelCell(rowContent, 2, question.Content);
                    AddExcelCell(rowContent, 3, question.Answer);
                    AddExcelCell(rowContent, 4, question.Explain);
                    i++;
                }

                workbook.Write(fs);
            }
            return fileName;
        }

        private void AddExcelHead(IWorkbook workbook, IRow row, int col, string value)
        {
            if(HeadStyle == null)
            {
                var HeadStyle = workbook.CreateCellStyle();
                HeadStyle.FillForegroundColor = HSSFColor.BrightGreen.Blue.Index2;
                HeadStyle.FillPattern = FillPattern.SolidForeground;
            }

            var cell = row.CreateCell(col);
            cell.CellStyle = HeadStyle;
            cell.SetCellValue(value);
        }
        private void AddExcelCell(IRow row, int col, string value)
        {
            var cell = row.CreateCell(col);
            cell.SetCellValue(value);
        }
        #endregion

        private void AddHead(XWPFDocument doc, string head)
        {
            var p0 = doc.CreateParagraph();
            p0.Alignment = ParagraphAlignment.CENTER;
            XWPFRun r0 = p0.CreateRun();
            r0.FontFamily = "microsoft yahei";
            r0.FontSize = 18;
            r0.IsBold = true;
            r0.SetText(head);
        }

        private void AddContent(XWPFDocument doc, string content)
        {
            var p1 = doc.CreateParagraph();
            p1.Alignment = ParagraphAlignment.LEFT;
            p1.IndentationFirstLine = 500;
            XWPFRun r1 = p1.CreateRun();
            r1.FontFamily = "microsoft yahei";
            r1.FontSize = 12;
            r1.IsBold = true;
            r1.SetText(content);
        }

        private void AddPageBreak(XWPFDocument doc)
        {
            var p = doc.CreateParagraph();
            p.IsPageBreak = true;
        }
    }
}
